package com.wanmait.schedule.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.UpdateWrapper;
import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.github.pagehelper.PageHelper;
import com.github.pagehelper.PageInfo;
import com.wanmait.schedule.entity.*;
//import com.wanmait.schedule.esRepository.ProjectRepository;
import com.wanmait.schedule.mapper.*;
import com.wanmait.schedule.service.*;
import com.wanmait.schedule.entity.*;
import com.wanmait.schedule.mapper.*;
import com.wanmait.schedule.service.*;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.wanmait.schedule.service.TaskService;
import lombok.extern.slf4j.Slf4j;
import org.apache.ibatis.annotations.Options;
import org.apache.ibatis.annotations.Param;
import org.elasticsearch.index.query.QueryBuilders;
import org.elasticsearch.search.fetch.subphase.highlight.HighlightBuilder;
import org.elasticsearch.search.sort.SortBuilders;
import org.elasticsearch.search.sort.SortOrder;
import org.springframework.data.domain.PageRequest;
import org.springframework.data.elasticsearch.core.ElasticsearchRestTemplate;
import org.springframework.data.elasticsearch.core.SearchHits;
import org.springframework.data.elasticsearch.core.query.NativeSearchQuery;
import org.springframework.data.elasticsearch.core.query.NativeSearchQueryBuilder;
import org.springframework.stereotype.Service;

import javax.annotation.Resource;
import java.util.List;
import java.text.SimpleDateFormat;
import java.time.LocalDate;
import java.time.LocalDateTime;
import java.util.ArrayList;
import java.util.HashSet;
import java.util.*;
import java.util.Set;
import java.text.SimpleDateFormat;
import java.time.LocalDate;
import java.time.LocalDateTime;
import java.util.ArrayList;
import java.util.HashSet;
import java.util.*;
import java.util.Set;

/**
 * <p>
 * 项目表 服务实现类
 * </p>
 *
 * @author wanmait
 * @since 2022-03-02
 */
@Service
@Slf4j
public class ProjectServiceImpl extends ServiceImpl<ProjectMapper, Project> implements ProjectService {
    @Resource
    private ProjectMapper projectMapper;
    @Resource
    private DepartmentService departmentService;
    @Resource
    private DepartmentMapper departmentMapper;
    @Resource
    private CompanyUserMapper companyUserMapper;
    @Resource
    private StateMapper stateMapper;
    @Resource
    private CompanyService companyService;
    @Resource
    private TaskService taskService;
    @Resource
    private RejectService rejectService;
    @Resource
    private DataService dataService;
    @Resource
    private ElasticsearchRestTemplate elasticsearchRestTemplate;
    @Resource
    private UserinfoMapper userinfoMapper;
//    @Resource
//    private ProjectRepository projectRepository;

    //通过企业用户id查询所有的项目
    @Override
    public List<Project> findAllProject(Integer companyUserId) {
        LambdaQueryWrapper<Project> lambdaQueryWrapper=new LambdaQueryWrapper<>();
        lambdaQueryWrapper.eq(Project::getCompanyUserId,companyUserId);
        lambdaQueryWrapper.orderByDesc(Project::getPubTime);
        List<Project> projects=this.list(lambdaQueryWrapper);
        return projects;
    }

    @Override
    public Page<Project> selectProjectByPage(Integer pageSize, Integer pageNum,Integer companyUserId) {
        Page<Project> page = new Page<Project>(pageNum,pageSize);
        LambdaQueryWrapper<Project> queryWrapper = new LambdaQueryWrapper<>();
        queryWrapper.orderByDesc(Project::getCompanyUserId);
        queryWrapper.eq(Project::getCompanyUserId,companyUserId);
        queryWrapper.eq(Project::getSubmit,false);
        return projectMapper.selectPage(page,queryWrapper);
    }

    @Override
    public Project selectOneProjectById(Integer projectId) {
        Project project = new Project();
        project = this.getById(projectId);
        Department department = new Department();
        department = departmentService.getById(project.getDepartmentId());
        project.setDepartment(department);
        return project;
    }

    @Override
    public PageInfo<Project> findPage(Integer pageNum, Integer pageSize,Integer companyId) {
        PageHelper.startPage(pageNum,pageSize);
        LambdaQueryWrapper<Project> queryWrapper = new LambdaQueryWrapper<>();
        queryWrapper.eq(Project::getCompanyId,companyId);
        List<Project> projects = this.list(queryWrapper);

        projects.forEach(project -> {
            project.setDepartment(departmentService.getById(project.getDepartmentId()));

            CompanyUser companyUser = companyUserMapper.selectById(project.getCompanyUserId());
            companyUser.setUserinfo(userinfoMapper.selectById(companyUser.getUserinfoId()));

            project.setCompanyUser(companyUser);
        });
        PageInfo<Project> pageInfo = new PageInfo<>(projects);
        return pageInfo;
    }

    @Override
    public Boolean updateProjectFindById(Project project) {
        if (project.getId()!=null) {
            LambdaQueryWrapper<Project> queryWrapper = new LambdaQueryWrapper<>();
            queryWrapper.eq(Project::getId, project.getId());
            projectMapper.update(project, queryWrapper);
            return true;
        }
        else {
            return false;
        }
    }

    @Override
    public PageInfo<Project> projectFindAll(Integer pageNum,Integer pageSize,Integer companyId) {
        PageHelper.startPage(pageNum,pageSize);
        LambdaQueryWrapper<Project> queryWrapper = new LambdaQueryWrapper<>();
        queryWrapper.eq(Project::getCompanyId,companyId);
        List<Project> projects = this.list(queryWrapper);
        Map<String,Object> map = new HashMap<>();
        projects.forEach(project -> {
            project.setDepartment(departmentService.getById(project.getDepartmentId()));
            map.put("project_id",project.getId());
            project.setTaskList(taskService.getBaseMapper().selectByMap(map));
        });
        PageInfo<Project> pageInfo = new PageInfo<>(projects);
        return pageInfo;
    }

    @Override
    public boolean release(Project project) {
        if (project.getDepartmentId()!=null){
            LambdaQueryWrapper<CompanyUser> companyUserQueryWrapper = new LambdaQueryWrapper<>();
            companyUserQueryWrapper.eq(CompanyUser::getDepartmentId,project.getDepartmentId());
            companyUserQueryWrapper.eq(CompanyUser::getPositionId,2);
            CompanyUser companyUser = companyUserMapper.selectOne(companyUserQueryWrapper);
            if (companyUser != null){
                project.setCompanyUserId(companyUser.getId());
                projectMapper.insert(project);
                State state = new State();
                state.setProjectId(project.getId());
                state.setProjectState(0);
                state.setStateTime(LocalDateTime.now());
                stateMapper.insert(state);
                return true;
            }
        }
        else {
            projectMapper.insert(project);
            return true;
        }
        return false;
    }

    @Override
    public List<Task> taskList(Integer id) {
        LambdaQueryWrapper<Task> queryWrapper = new LambdaQueryWrapper<>();
        queryWrapper.eq(Task::getProjectId,id);
        List<Task> taskList = taskService.list(queryWrapper);
        Map<String,Object> map = new HashMap<>();
        taskList.forEach(task -> {
            map.put("task_id",task.getId());
            task.setDataList(dataService.getBaseMapper().selectByMap(map));
        });
        return taskList;
    }

    @Override
    public Boolean submitProject(Integer projectId) {
//        检查这个项目下的任务是否已经全部审核通过提交
        LambdaQueryWrapper<Task> queryWrapper = new LambdaQueryWrapper();
        queryWrapper.eq(Task::getProjectId,projectId);
        queryWrapper.eq(Task::getIspass,false);
        List<Task> taskList =  taskService.list(queryWrapper);
        log.info("长度"+String.valueOf(taskList.size()));
        if(taskList.size()==0){
//            修改project表中的submit
            Project project = new Project();
            project.setSubmit(true);
            UpdateWrapper<Project> updateWrapper = new UpdateWrapper<>();
            updateWrapper.eq("id",projectId);
            this.update(project,updateWrapper);
            return true;
        }
        return false;
    }

    @Override
    public List<Reject> rejectProjectList(Integer companyUserId) {
        LambdaQueryWrapper<Project> projectLambdaQueryWrapper = new LambdaQueryWrapper<>();
        projectLambdaQueryWrapper.eq(Project::getCompanyUserId,companyUserId).eq(Project::getSubmit,false);
        List<Project>projectList = this.list(projectLambdaQueryWrapper);
        Set<Integer> integerSet = new HashSet<>();
        projectList.forEach(project -> {
            integerSet.add(project.getId());
        });
        List<Reject> rejectList = new ArrayList<>();
        LambdaQueryWrapper<Reject> rejectLambdaQueryWrapper = new LambdaQueryWrapper<>();
        if(!integerSet.isEmpty()){
            rejectLambdaQueryWrapper.in(Reject::getProjectId,integerSet ).isNull(Reject::getTaskId);
            rejectList = rejectService.list(rejectLambdaQueryWrapper);
            rejectList.forEach(reject -> {
                reject.setProject(this.getById(reject.getProjectId()));
            });
            return rejectList;
        }
        return null ;
    }
   /* @Override
    public List<Project> selectNoSubmitProjects(Integer id ,String keyword) {
//        LambdaQueryWrapper<Project> queryWrapper = new LambdaQueryWrapper<>();
//        queryWrapper.eq(Project::getCompanyUserId,companyUserId).eq(Project::getSubmit,false);
//        List<Project> projects = projectRepository.findAllByNameMatchesAndDetailsMatches(keyword,keyword);
        List<Project> projects = projectRepository.findProjectsByCompanyUserIdAndNameMatchesAndSubmitFalse(id,keyword);
        return projects;
    }
    @Override
    public List<Project> selectNoSubmitProjects2(Integer id ) {
        List<Project> projects = projectRepository.findProjectsByCompanyUserIdAndSubmitFalse(id);
        return projects;
    }*/

    @Override
    public List<Project> search(String searchContent) {
        //构建NativeSearchQueryBuilder查询对象
        NativeSearchQueryBuilder searchQueryBuilder = new NativeSearchQueryBuilder();
        //使用QueryBuilders指定查询条件和查询类型
        searchQueryBuilder.withQuery(QueryBuilders.matchQuery("name",searchContent));
        //使用SortBuilders指定排序字段和排序方式
        //searchQueryBuilder.withSorts(SortBuilders.fieldSort("name").order(SortOrder.DESC));
        //使用PageRequest对象指定分页参数
        searchQueryBuilder.withPageable(PageRequest.of(0,2));
        //设置高亮
        HighlightBuilder highlightBuilder = new HighlightBuilder();
        //默认高亮字段使用<em></em>标签
        highlightBuilder.field("name");
        highlightBuilder.field("title").preTags("<span style=\"color:red\">").postTags("</span>");
        searchQueryBuilder.withHighlightBuilder(highlightBuilder);

        //构建查询对象
        NativeSearchQuery searchQuery = searchQueryBuilder.build();

        //执行查询
        SearchHits<Project> searchHits = elasticsearchRestTemplate.search(searchQuery,Project.class);

        //条数
        System.out.println(searchHits.getTotalHits());
        //如果想单独查询条数
        long count = elasticsearchRestTemplate.count(searchQuery,Project.class);
        System.out.println(count);

        List<Project> projects = new ArrayList<>();
        searchHits.forEach(searchHit-> {
            //Map<String,List<String>> map = searchHit.getHighlightFields();
            Project project = searchHit.getContent();
            List<String> names = searchHit.getHighlightField("name");
            project.setName(names.get(0));
            projects.add(project);
        });

        projects.forEach(project -> System.out.println(project.getId()+project.getName()));
        return projects;
    }

    @Override
    public List<CompanyUser> initCompanyUser(Integer companyId) {
        LambdaQueryWrapper<CompanyUser> queryWrapper  = new LambdaQueryWrapper<>();
        queryWrapper.eq(CompanyUser::getCompanyId,companyId);
        List<CompanyUser> companyUserList = companyUserMapper.selectList(queryWrapper);
        companyUserList.forEach(companyUser -> {
            Userinfo userinfo = userinfoMapper.selectById(companyUser.getUserinfoId());
            companyUser.setUsername(userinfo.getName());
        });
        return companyUserList;
    }




}
